﻿using System.Collections.Generic;
using System.Linq;
using Sustainalytics.Reporting.Framework;
using Foxit.PDF.PageElements;
using Foxit.PDF;
using Sustainalytics.RiskRatings.Reporting.Charts;
using Sustainalytics.Entities.RiskRatings;
using Foxit.PDF.Imaging;
using System;
using System.Text;

namespace Sustainalytics.RiskRatings.Reporting
{
    public class MaterialEsgIssuesSection : PdfReportSectionGenerator
    {
        public MaterialEsgIssuesSection(int index):base(index)
        {
            this._reportSection.Name = "MEI section";
        }

        float ColumnWidth;
        float XRightColumn;
        private float Event_CurrentXOffset { get; set; }
        private float Event_LeftYOffset { get; set; }
        private float Event_CurrentYOffset { get; set; }
        private PdfReportPage CurrentPage { get; set; }
        private bool MeiSecondPage { get; set; }
        private RiskRatingMaterialEsgIssueBase CurrentIssue { get; set; }

        public override void ComposeSectionContent()
        {
            if (_dataSource.CompanyProfile.MaterialEsgIssues.Any())
            {
                ColumnWidth = (_report.PageMaxWidth - (float)HorisontalSpacing.Large) / 2;
                OutlinePageCount = 0;
                XRightColumn = ColumnWidth + (float)HorisontalSpacing.Large;

                var sortedList = _dataSource.CompanyProfile.MaterialEsgIssues.ToList()
                                    .FindAll(x => x.Type == MaterialIssueType.MaterialIssue || x.Type == MaterialIssueType.IdiosyncraticIssue)
                                    .OrderBy(y => y.SortKey.Value).ToList();

                foreach (var issue in sortedList)
                {
                    var page = new PdfReportPage_MaterialIssues(_report, _dataSource, issue, ReportHelper.GetMeiImage(issue.ExternalId.ToString(), MeiImageColor.Colored, MeiImageSize.Large, issue.Type == MaterialIssueType.IdiosyncraticIssue));
                    _report.Pages.Add(page);
                    OutlinePageCount++;
                    float currentYOffset = page.Top;
                    OutlinePositions.Add(new OutlinePosition { Name = issue.Name, PageNumber = OutlinePageCount, VerticalPosition = page.Top - HeaderHeight });

                    if (issue.Type == MaterialIssueType.IdiosyncraticIssue)
                    {
                        currentYOffset += (float)VerticalSpacing.Small;

                        currentYOffset=AddRatingDetails(issue, page, 0, currentYOffset, ColumnWidth);
                        
                        AddMaterialIssues_EventsPage(issue, 0, currentYOffset, _report.PageMaxWidth, page);
                    }
                    else
                    {
                        MeiSecondPage = false;
                        AddMaterialIssues_FirstPage(issue, page, 0, currentYOffset-5f, _report.PageMaxWidth);
                        if (!MeiSecondPage)
                        {
                            page = new PdfReportPage_MaterialIssues(_report, _dataSource, issue, ReportHelper.GetMeiImage(issue.ExternalId.ToString(), MeiImageColor.Colored, MeiImageSize.Large));
                            _report.Pages.Add(page);
                            OutlinePageCount++;
                            currentYOffset = page.Top;
                            //eventual schimbat currentYOffset
                            AddMaterialIssues_SecondPage(issue, page, 0, currentYOffset, _report.PageMaxWidth, _report.Pages.Count());
                        }
                        
                        
                    }
                }
            }
        }

        #region Mei Details section

        private void AddMaterialIssues_FirstPage(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            float currentYOffset_Left = y + (float)VerticalSpacing.Small;
            float currentYOffset_Right = y + (float)VerticalSpacing.Small;
            var columnWidth = (maxWidth - (float)HorisontalSpacing.Large) / 3;
            var firstSectionWidth = (maxWidth - (float)HorisontalSpacing.Large) / 2;
            page.Elements.Add(new Line(x, y-10f, x + maxWidth, y-10f, 1, Colors.LineColor));
            currentYOffset_Left = AddIssueEsgRiskRating(issue, page, x, y, firstSectionWidth);
            var yRiskAnalysisSection = currentYOffset_Left;
            var yExp = AddIssueRiskAnalysisExposure(issue, page, x, yRiskAnalysisSection - 5f, ColumnWidth);
            var yMag = AddIssueRiskAnalysisManagement(issue, page, x, yRiskAnalysisSection - 5f, ColumnWidth);
            currentYOffset_Left = AddIssueRiskAnalysisScatterChart(issue, page, x, yRiskAnalysisSection, ColumnWidth);
            currentYOffset_Left = Math.Max(Math.Max(yExp, yMag), currentYOffset_Left);
            currentYOffset_Left = RiskDetailsChart(issue, page, x, currentYOffset_Left, columnWidth);

            currentYOffset_Left = Math.Max(currentYOffset_Left, currentYOffset_Right);
            
            currentYOffset_Left += (float)VerticalSpacing.Small;

        }

        private void AddKeyIssueSubIndustryComparison(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            float currentYOffset = y + (float)VerticalSpacing.Small;
            page.Elements.Add(new Label($"Subindustry Overview – {_dataSource.CompanyProfile.SubPeerGroup}", x, currentYOffset, maxWidth,
                (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));
            currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small+5;
            MaterialEsgIssuesBenchmark meiBenchmark = new MaterialEsgIssuesBenchmark();
            if (_dataSource.Benchmark.MaterialEsgIssueBenchmarks != null)
                meiBenchmark = _dataSource.Benchmark.MaterialEsgIssueBenchmarks.FirstOrDefault(a => a.MeiExternalId == issue.ExternalId);
            if (meiBenchmark != null)
            {
                page.Elements.Add(new Label("Subindustry Exposure/Management", x, currentYOffset, ColumnWidth, 8, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Black));
                page.Elements.Add(new Label("Peers Comparison", XRightColumn, currentYOffset, maxWidth, 8, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Black));
                currentYOffset += 25;

                var chart = new RiskRating_ScatterChart(x, currentYOffset, maxWidth)
                {
                    SubPeerGroupBenchmark = meiBenchmark.PeersList,
                    ShowGridLines = true,
                    ChartType = ScatterChartType.MatterialIssue,
                    CompanyId = _dataSource.CompanyId,
                    SubIndustryDataPoints = _dataSource.SubIndustryMEIRiskRatingPerformanceDictionary.ContainsKey(issue.ExternalId) ? _dataSource.SubIndustryMEIRiskRatingPerformanceDictionary[issue.ExternalId] : new List<SubIndustryRiskRatingPerformance>(),
                    MarketCapMin = (float)meiBenchmark.MarketCapMin,
                    MarketCapMax = (float)meiBenchmark.MarketCapMax,
                    RiskRatingClusterList = _dataSource.OverallClusters
                };
                page.Elements.Add(chart);
            }
        }

        private float AddAnalystCommentary(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            float currentYOffset = y;
            var comentaryTitle = string.Format(issue.IsMain.Value ? "Analyst View – {0}" : "Subindustry Narrativetest – {0}", issue.Name);
            var labelTitle = new Label(comentaryTitle, x, currentYOffset, maxWidth,
                    (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black);
            currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;
            Label lblExposureTitle = null, lblManagmentTitle = null, lblConclusionTitle = null;
            var commentSections = 0;
            var displayTitle = false;

            if (issue.IsMain.Value)
            {
                if (!string.IsNullOrWhiteSpace(issue.ExposureComment?.Value))
                {
                    lblExposureTitle = new Label("Exposure", x, currentYOffset, maxWidth,
                                    (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black);
                    currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;
                    FormattedTextArea textArea = new FormattedTextArea(issue.ExposureComment.Value, x, currentYOffset, maxWidth, 500, Fonts.RobotoFontFamily, 7, false);
                    page.Elements.Add(textArea);
                    displayTitle = true;
                    currentYOffset += textArea.GetRequiredHeight() + (float)VerticalSpacing.Small;
                    commentSections++;
                }

                if (!string.IsNullOrWhiteSpace(issue.ManagementComment?.Value))
                {
                    lblManagmentTitle = new Label("Management", x, currentYOffset, maxWidth,
                                    (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black);
                    currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;
                    FormattedTextArea textArea = new FormattedTextArea(issue.ManagementComment.Value, x, currentYOffset, maxWidth, 500, Fonts.RobotoFontFamily, 7, false);
                    page.Elements.Add(textArea);
                    displayTitle = true;
                    currentYOffset += textArea.GetRequiredHeight() + (float)VerticalSpacing.Small;
                    commentSections++;
                }

                if (!string.IsNullOrWhiteSpace(issue.AnalystViewComment?.Value))
                {
                    lblConclusionTitle = new Label("Conclusion", x, currentYOffset, maxWidth,
                                    (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black);
                    currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;
                    FormattedTextArea textArea = new FormattedTextArea(issue.AnalystViewComment.Value, x, currentYOffset, maxWidth, 500, Fonts.RobotoFontFamily, 7, false);
                    page.Elements.Add(textArea);
                    displayTitle = true;
                    currentYOffset += textArea.GetRequiredHeight() + (float)VerticalSpacing.Small;
                    commentSections++;
                }

                if (commentSections > 1)
                {
                    if (lblExposureTitle != null)
                        page.Elements.Add(lblExposureTitle);
                    if (lblConclusionTitle != null)
                        page.Elements.Add(lblConclusionTitle);
                    if (lblManagmentTitle != null)
                        page.Elements.Add(lblManagmentTitle);
                }
            }
            else
            {
                if (!string.IsNullOrWhiteSpace(issue.Narrative?.Value))
                {
                    FormattedTextArea textArea = new FormattedTextArea(issue.Narrative.Value, x, currentYOffset, maxWidth, 500, Fonts.RobotoFontFamily, 7, false);
                    page.Elements.Add(textArea);
                    displayTitle = true;
                    currentYOffset += textArea.GetRequiredHeight() + (float)VerticalSpacing.Small;
                }
            }

            if (displayTitle)
            {
                page.Elements.Add(labelTitle);
            }
            else
            {
                currentYOffset = y;
            }
            return currentYOffset;
        }

        private float AddSubIndustryBenchmark(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            float currentYOffset = y + (float)VerticalSpacing.Small;

            page.Elements.Add(new Label("Risk Rating Distribution", x, currentYOffset, maxWidth, (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));
            currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;

            var chartPoints = _dataSource.SubIndustryMEIAggregateDataPointsDictionary.ContainsKey(issue.ExternalId) ? _dataSource.SubIndustryMEIAggregateDataPointsDictionary[issue.ExternalId].Data : Enumerable.Empty<RiskRatingDataPoint>();
            if (chartPoints.Any())
            {
                RiskRating_CustomColumnChartGroup chartObj = new RiskRating_CustomColumnChartGroup();
                chartObj.Left = x;
                chartObj.Top = currentYOffset + 10f;
                chartObj.Width = maxWidth;
                chartObj.Height = 210;
                chartObj.RiskRatingClusterList = _dataSource.OverallClusters;
                chartObj.UniverseChartValues = null;
                chartObj.IndustryChartValues = null;
                chartObj.SubIndustryChartValues = chartPoints;
                page.Elements.Add(chartObj);

                currentYOffset += 200;
            }
            return currentYOffset;
        }

        private float AddIssueRiskAnalysisExposure(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            var currentYOffset = y;
            var width = page.Dimensions.Width;
            var issue_risk_details = ReportHelper.GetFile("icon-risk-analysis.png");
            page.Elements.Add(new Image(ImageData.GetImage(issue_risk_details), x, currentYOffset - 13f, 0.25f));
            page.Elements.Add(new Label("Risk Analysis", x + 30f, currentYOffset - 6f, 100f, 12f, Fonts.MontserratBold, 10f, TextAlign.Left, RgbColor.Black));
            page.Elements.Add(new Line(x + 140, currentYOffset, _report.PageMaxWidth, currentYOffset, 1, RgbColor.Black));

            currentYOffset += 20;

            var columnWidth = width / 3 - 20f;
            page.Elements.Add(new Label("Exposure Score", x + 3f, currentYOffset, maxWidth, 10, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Black));
            currentYOffset += 15;
            var exposureScore = issue.ManagementRisk.Exposure.Value.ToString("#0.0");
            var assesment = issue.ExposureCluster.ToString();

            page.Elements.Add(new Label(exposureScore, x + 3f, currentYOffset + 15f, maxWidth, 10, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Black));
            page.Elements.Add(new Label(" /20+", x + 18f, currentYOffset + 15f, maxWidth, 10, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Gray));
            page.Elements.Add(new Label(assesment, x + 40f, currentYOffset + 15f, maxWidth, 10, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Black));
            page.Elements.Add(new Label(string.Format("Beta = {0}", issue.FinalBetaFactor.Value.ToString("#0.00")), x + 3f, currentYOffset + 30f, maxWidth, 6, Fonts.RobotoBold, 6, TextAlign.Left, RgbColor.Black));

            RiskRating_RiskAnalysisRangeChart chartObjExposure = new RiskRating_RiskAnalysisRangeChart();
            chartObjExposure.Top = currentYOffset + 5f;
            chartObjExposure.Left = x + 75f;
            chartObjExposure.Width = 30f;
            chartObjExposure.Type = "Exposure";
            chartObjExposure.ChartType = RiskChartType.MEI;
            chartObjExposure.SubIndustryValue = (float)issue.SubIndustryExposureScore.Value;
            chartObjExposure.Value = (float)issue.ManagementRisk.Exposure.Value;
            chartObjExposure.Assessment = assesment;
            chartObjExposure.ExposureClusterList = _dataSource.ExposureClusters.Where(s => s.Type == RiskRatingClusterType.MEI).ToList();
            page.Elements.Add(chartObjExposure);

            currentYOffset += 45;

            var style = new FormattedTextAreaStyle(Fonts.RobotoFontFamily, 6f, false)
            {
                Paragraph = { Align = TextAlign.Left, Indent = 0, SpacingAfter = 0, AllowOrphanLines = false }
            };
            var exposureText = String.Empty;

            if (issue.IsMain.Value == false)
            {
                exposureText += issue.Narrative.Value.ToString();
            }
            else
            {
                if (issue.ExposureComment != null && issue.ExposureComment.Value != null)
                    exposureText = issue.ExposureComment.Value;
            }
            if (issue.AnalystViewExposureAssessment != null && issue.AnalystViewExposureAssessment.Value != null)
                exposureText += issue.AnalystViewExposureAssessment.Value;
 
            var formattedTextArea = new FormattedTextArea(exposureText, x + 3f, currentYOffset + 7f, columnWidth - 10f, 600f, style);
            var textAreaHeight = formattedTextArea.GetRequiredHeight();

            if (textAreaHeight + currentYOffset > _report.PageDimensions.Body.Height)
            {
                textAreaHeight = _report.PageDimensions.Body.Height - currentYOffset - 10f;
                page.Elements.Add(new Label("...", x + columnWidth - 8f, currentYOffset + textAreaHeight - 5f, maxWidth, 8, Fonts.RobotoRegular, 6, TextAlign.Left, RgbColor.Black));
            }

            formattedTextArea = new FormattedTextArea(exposureText, x + 3f, currentYOffset + 7f, columnWidth - 10f, textAreaHeight, style);

            page.Elements.Add(formattedTextArea);
            currentYOffset += textAreaHeight + 10f;

            return currentYOffset;
        }


        private float AddIssueRiskAnalysisManagement(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            var currentYOffset = y;
            var width = page.Dimensions.Width;

            currentYOffset += 20;

            var columnWidth = width / 3 - 20f;
            x = columnWidth;
            page.Elements.Add(new Label("Management Score", x + 3f, currentYOffset, maxWidth, 10, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Black));
            currentYOffset += 15;
            var managementScore = issue.ManagementRisk.Management.Value.ToString("#0.0");
            var assesment = issue.ManagementCluster.ToString();

            page.Elements.Add(new Label(managementScore, x + 3f, currentYOffset + 15f, maxWidth, 10, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Black));
            page.Elements.Add(new Label(" /100", x + 18f, currentYOffset + 15f, maxWidth, 10, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Gray));
            page.Elements.Add(new Label(assesment, x + 40f, currentYOffset + 15f, maxWidth, 10, Fonts.RobotoRegular, 8, TextAlign.Left, RgbColor.Black));

            RiskRating_RiskAnalysisRangeChart chartObjManagement = new RiskRating_RiskAnalysisRangeChart();
            chartObjManagement.Top = currentYOffset + 5f;
            chartObjManagement.Left = x + 75f;
            chartObjManagement.Width = 20f;
            chartObjManagement.Type = "Management";
            chartObjManagement.Value = (float)issue.ManagementRisk.Management.Value;
            chartObjManagement.Assessment = assesment;
            chartObjManagement.ManagementClusterList = _dataSource.ManagementClusters.Where(s => s.Type == RiskRatingClusterType.MEI).ToList();
            page.Elements.Add(chartObjManagement);

            currentYOffset += 45;

            var style = new FormattedTextAreaStyle(Fonts.RobotoFontFamily, 6f, false)
            {
                Paragraph = { Align = TextAlign.Left, Indent = 0, SpacingAfter = 0, AllowOrphanLines = false }
            };

            var managementText = String.Empty;
            if (issue.IsMain.Value == true)
            {
                if (issue.ManagementComment != null && issue.ManagementComment.Value != null)
                    managementText = issue.ManagementComment.Value;
            }
            if (issue.AnalystViewManagementAssessment != null && issue.AnalystViewManagementAssessment.Value != null)
                managementText += issue.AnalystViewManagementAssessment.Value;

            var formattedTextArea = new FormattedTextArea(managementText, x + 3f, currentYOffset + 7f, columnWidth - 10f, 600f, style);
            var textAreaHeight = formattedTextArea.GetRequiredHeight();

            if (textAreaHeight + currentYOffset > _report.PageDimensions.Body.Height)
            {
                textAreaHeight = _report.PageDimensions.Body.Height - currentYOffset - 10f;
                page.Elements.Add(new Label("...", x + columnWidth - 8f, currentYOffset + textAreaHeight - 5f, maxWidth, 8, Fonts.RobotoRegular, 6, TextAlign.Left, RgbColor.Black));
            }
            formattedTextArea = new FormattedTextArea(managementText, x + 3f, currentYOffset + 7f, columnWidth - 10f, textAreaHeight, style);

            page.Elements.Add(formattedTextArea);

            currentYOffset += textAreaHeight + 10f;

            return currentYOffset;
        }


        private float AddIssueRiskAnalysisScatterChart(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            var currentYOffset = y;
            var width = page.Dimensions.Width;
            x = width * 2;
            var columnWidth = width / 3 - 20f;
   
            double meiSubIndustryExp=0;
            double meiSubIndustryManagement=0;
            foreach ( var meiBenchmark in _dataSource.Benchmark.MaterialEsgIssueBenchmarks)
            {
                if (meiBenchmark.MeiExternalId == issue.ExternalId)
                {

                    meiSubIndustryExp = meiBenchmark.SubIndustryPerformanceExposure.Average;
                    meiSubIndustryManagement = meiBenchmark.SubIndustryPerformanceManagement.Average;
                }

            }
            var MeiManagement = issue.ManagementRisk.Management.Value;
            var MeiExposure = issue.ManagementRisk.Exposure.Value;
            var chart = new RiskRating_ScatterChart(columnWidth + (float)HorisontalSpacing.Large +150f, currentYOffset + 10, columnWidth)
            {

                SubPeerGroupBenchmark = _dataSource.Benchmark.MaterialEsgIssueBenchmarks.First(mei => mei.MeiExternalId == issue.ExternalId).PeersList,
                ShowGridLines = true,
                ChartType = ScatterChartType.MatterialIssue,
                CompanyId =_dataSource.CompanyId,
                MeiExposure=MeiExposure,
                MeiManagament=MeiManagement,
                SubIndustryMEIAvgExposure=meiSubIndustryExp,
                SubIndustryMEIAvgManagement=meiSubIndustryManagement,
                SubIndustry = _dataSource.CompanyProfile.SubPeerGroup,
                SubIndustryDataPoints  = _dataSource.SubIndustryMEIRiskRatingPerformanceDictionary.ContainsKey(issue.ExternalId) ? _dataSource.SubIndustryMEIRiskRatingPerformanceDictionary[issue.ExternalId] : new List<SubIndustryRiskRatingPerformance>(),
                GlobalUniverseDataPoints = _dataSource.GlobalUniverseMEIRiskRatingPerformanceDictionary.ContainsKey(issue.ExternalId) ? _dataSource.GlobalUniverseMEIRiskRatingPerformanceDictionary[issue.ExternalId] : new List<GlobalUniverseRiskRatingPerformance>(),
                RiskRatingClusterList = _dataSource.OverallClusters
            };
            page.Elements.Add(chart);
            currentYOffset += 190f;
            return currentYOffset;
        }

        private float RiskDetailsChart(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            float currentYOffset = y;
            if ((250f+currentYOffset) > (_report.PageDimensions.Body.Height))
            {
                page = new PdfReportPage_MaterialIssues(_report, _dataSource, issue, ReportHelper.GetMeiImage(issue.ExternalId.ToString(), MeiImageColor.Colored, MeiImageSize.Large));
                _report.Pages.Add(page);
                OutlinePageCount++;
                currentYOffset = 45f;
                MeiSecondPage = true;
            }
            RiskRating_RiskRangeBarChart chartObj = new RiskRating_RiskRangeBarChart();
            chartObj.Left = x;
            chartObj.Top = currentYOffset+50f;
            chartObj.Width = maxWidth;
            chartObj.Value1 = issue.ManagementRisk.Exposure.Value;
            chartObj.Value2 = issue.ManagementRisk.ManageableRisk.Value;
            chartObj.Value3 = issue.ManagementRisk.ManagedRisk.Value;
            chartObj.Value4 = issue.ManagementRisk.ManagementGap.Value;
            chartObj.Value5 = issue.ManagementRisk.UnmanageableRisk.Value;
            chartObj.Value6 = issue.ManagementRisk.UnmanagedRisk.Value;
            chartObj.BarHeight = 10f;
            chartObj.ChartType = RiskRangeChartType.IssueRiskDetails;
            page.Elements.Add(chartObj);
            currentYOffset += currentYOffset;
            if (MeiSecondPage)
            {
                currentYOffset += 230f;
                AddMaterialIssues_SecondPage(issue, page, 0, currentYOffset, _report.PageMaxWidth, _report.Pages.Count());
            }
          
            return currentYOffset;

        }

        private float AddIssueEsgRiskRating(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            float currentYOffset = y-5f;
            float value1 = (float)issue.ManagementRisk.UnmanagedRisk.Value;
 
            page.Elements.Add(new Label("Rating Overview", x, currentYOffset, maxWidth, 10.5f+2f, Fonts.RobotoBold, 10.5f, TextAlign.Left, RgbColor.Black));
            currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;
            currentYOffset += 10f;
            page.Elements.Add(new RiskRating_CustomBulletChart
            {
                Top = currentYOffset,
                Left = x,
                Width = maxWidth,
                Value = value1,
                Assessment = issue.Cluster.Assessment.ToString(),
                RiskRatingClusterList = _dataSource.MaterialIssuesClusters,
                BarHeight = 15
            });
            currentYOffset += 60;
         
            var analystComment = String.Empty;
            if (issue.AnalystViewComment.Value != null)
            {
                //add this section only if the comment exist
                analystComment = issue.AnalystViewComment.Value;
                
                var style = new FormattedTextAreaStyle(Fonts.RobotoFontFamily, 7f, false)
                {
                    Paragraph = { Align = TextAlign.Left, Indent = 0, SpacingAfter = 0, AllowOrphanLines = false }
                };
                var analystCommentTextArea = new FormattedTextArea(analystComment, x + 10f, currentYOffset + 20, x + maxWidth - 20f, 45f, style);
                page.Elements.Add(new Line(x, currentYOffset + 35f, x + maxWidth, currentYOffset + 35f, analystCommentTextArea.GetRequiredHeight()+15f, new RgbColor(236, 241, 246)));
                page.Elements.Add(analystCommentTextArea);
            }

            maxWidth = _report.PageMaxWidth / 2;

            var left = maxWidth;
            var top = y + (float)VerticalSpacing.Small-10f;

            AddRiskRatingDistribution(issue, page, left, top, maxWidth);

            top += 140f;

            AddRelativePerformance(issue, page, left, top, maxWidth);

            currentYOffset -= 20f;
            currentYOffset += 185f;
            return currentYOffset;
        }

        private void AddRiskRatingDistribution(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float left, float top, float maxWidth)
        {
            left += (float)HorisontalSpacing.Large;
            maxWidth -= (float)HorisontalSpacing.Large;

            float currentYOffset = top;

            page.Elements.Add(new Label("ESG Risk Rating Distribution", left, currentYOffset, maxWidth, 11, Fonts.RobotoBold, 8.5f, TextAlign.Left, RgbColor.Black));

            RiskRating_CustomColumnChartGroup chartObj = new RiskRating_CustomColumnChartGroup();
            chartObj.Left = left;
            chartObj.Top = currentYOffset-2f;
            chartObj.Width = maxWidth;
            chartObj.Height = 170;
            chartObj.RiskRatingClusterList = _dataSource.OverallClusters;
            chartObj.Assessment = issue.Cluster.Assessment.ToString();

            chartObj.UniverseChartValues = _dataSource.UniverseMEIAggregateDataPointsDictionary.ContainsKey(issue.ExternalId)
               ? _dataSource.UniverseMEIAggregateDataPointsDictionary[issue.ExternalId].Data
               : Enumerable.Empty<RiskRatingDataPoint>();
            chartObj.IndustryChartValues = _dataSource.IndustryMEIAggregateDataPointsDictionary.ContainsKey(issue.ExternalId)
               ? _dataSource.IndustryMEIAggregateDataPointsDictionary[issue.ExternalId].Data
               : Enumerable.Empty<RiskRatingDataPoint>();
            chartObj.SubIndustryChartValues = _dataSource.SubIndustryMEIAggregateDataPointsDictionary.ContainsKey(issue.ExternalId)
               ? _dataSource.SubIndustryMEIAggregateDataPointsDictionary[issue.ExternalId].Data
               : Enumerable.Empty<RiskRatingDataPoint>();

            page.Elements.Add(chartObj);
        }

        private void AddRelativePerformance(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float left, float top, float maxWidth)
        {
            left += (float)HorisontalSpacing.Large;
            maxWidth -= (float)HorisontalSpacing.Large;

            var meiBenchmark = _dataSource.Benchmark
                .MaterialEsgIssueBenchmarks
                .Where(x => x.MeiExternalId == issue.ExternalId)
                .SingleOrDefault();

            if (meiBenchmark == null) return;


            page.Elements.Add(new Label("Relative Performance", left, top, maxWidth, 11, Fonts.RobotoBold, 8.5f, TextAlign.Left, RgbColor.Black));
            top += 15;

            Table benchmarkTable = GetDefaultTable(left, top, maxWidth, 100);
            benchmarkTable.CellDefault.Border.Bottom.LineStyle = LineStyle.Dots;
            benchmarkTable.CellDefault.Border.Bottom.Width = 0.5f;
            benchmarkTable.CellDefault.Border.Color = RgbColor.Gray;
            benchmarkTable.CellDefault.VAlign = VAlign.Center;
            benchmarkTable.Columns.Add(maxWidth * 0.05f);
            benchmarkTable.Columns.Add(maxWidth * 0.45f);
            benchmarkTable.Columns.Add(maxWidth * 0.25f);
            benchmarkTable.Columns.Add(maxWidth * 0.25f);

            var row = benchmarkTable.Rows.Add(10);
            row.CellDefault.VAlign = VAlign.Center;
            row.Cells.Add(string.Empty);
            row.Cells.Add(string.Empty);
            row.Cells.Add("Rank", Fonts.RobotoBold, 7f);
            row.Cells.Add("Percentile", Fonts.RobotoBold, 7f);
            row.CellDefault.Border.Bottom.LineStyle = LineStyle.None;

            row = benchmarkTable.Rows.Add(10);
            row.CellDefault.VAlign = VAlign.Top;
            row.Cells.Add(string.Empty);
            row.Cells.Add(string.Empty);
            row.Cells.Add(new FormattedTextArea($"<p>(1<sup><font size='0'>st</font></sup> = lowest risk)</p>",
                0f, 0f, 60, 9f, Fonts.RobotoFontFamily, 7f, false));
            row.Cells.Add(new FormattedTextArea($"<p>(1<sup><font size='0'>st</font></sup> = lowest risk)</p>",
                0f, 0f, 60, 9f, Fonts.RobotoFontFamily, 7f, false));

            int percentile = 0;


            row = benchmarkTable.Rows.Add(20f);

            row.Cells.Add(new Rectangle(0f, 0f, 10f, 10f, new RgbColor(204, 204, 204), new RgbColor(204, 204, 204)));
            row.Cells.Add(new Label("Global Universe", 5f, 0f, 100f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            if (meiBenchmark.UniversePerformanceRisk != null)
            {
                row.Cells.Add(new FormattedTextArea(string.Format("<b>{0}</b> out of {1}",
                    meiBenchmark.UniversePerformanceRisk.Rank.ToString(),
                    meiBenchmark.UniversePerformanceRisk.Count.ToString()),
                    0f, 0f, maxWidth * 0.25f, 9f, Fonts.RobotoFontFamily, 7f, false));

                if (int.TryParse(Math.Round(meiBenchmark.UniversePerformanceRisk.Percentile * 100, 0, MidpointRounding.AwayFromZero).ToString(), out percentile))
                    row.Cells.Add(ReportHelper.AddOrdinal(percentile), Fonts.RobotoBold, 7f);
                else
                    row.Cells.Add("N/A", Fonts.RobotoBold, 7f);
            }
            else
            {
                row.Cells.Add(new FormattedTextArea("<b>{N/A}</b> out of {N/A}",
                        0f, 0f, maxWidth * 0.25f, 9f, Fonts.RobotoFontFamily, 7f, false));

                row.Cells.Add("N/A", Fonts.RobotoBold, 7f);
            }

            row = benchmarkTable.Rows.Add(20f);
            row.Cells.Add(new Rectangle(0f, 0f, 10f, 10f, new RgbColor(142, 175, 200), new RgbColor(142, 175, 200)));
            var industryName = _dataSource.CompanyProfile.PeerGroup + " (Industry Group)";
            var industryNameLenght = Fonts.RobotoRegular.GetTextWidth(industryName, 7);
            if (industryNameLenght > 100)
            {
                row.Cells.Add(new TextArea(industryName, 5f, 1f, 100f, 20f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            }
            else
            {
                row.Cells.Add(new Label(industryName, 5f, 0f, 100f, 9f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            }
            row.Cells.Add(new FormattedTextArea(string.Format("<b>{0}</b> out of {1}",
                meiBenchmark.IndustryPerformanceRisk.Rank.ToString(),
                meiBenchmark.IndustryPerformanceRisk.Count.ToString()),
                0f, 0f, maxWidth * 0.25f, 9f, Fonts.RobotoFontFamily, 7f, false));

            if (int.TryParse(Math.Round(meiBenchmark.IndustryPerformanceRisk.Percentile * 100, 0, MidpointRounding.AwayFromZero).ToString(), out percentile))
                row.Cells.Add(ReportHelper.AddOrdinal(percentile), Fonts.RobotoBold, 7f);
            else
                row.Cells.Add("N/A", Fonts.RobotoBold, 7f);

            page.Elements.Add(benchmarkTable);


            row = benchmarkTable.Rows.Add(20f);

            row.Cells.Add(new Rectangle(0f, 0f, 10f, 10f, new RgbColor(29, 96, 143), new RgbColor(29, 96, 143)));
            var subIndustryName = _dataSource.CompanyProfile.SubPeerGroup + " (Subindustry)";
            var subIndustryNameLenght = Fonts.RobotoRegular.GetTextWidth(subIndustryName, 7);
            if (subIndustryNameLenght > 100)
            {
                row.Cells.Add(new TextArea(subIndustryName, 5f, 1f, 100f, 20f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            }
            else
            {
                row.Cells.Add(new Label(subIndustryName, 5f, 0f, 100f, 9f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            }
            row.Cells.Add(new FormattedTextArea(string.Format("<b>{0}</b> out of {1}",
                meiBenchmark.SubIndustryPerformanceRisk.Rank.ToString(),
                meiBenchmark.SubIndustryPerformanceRisk.Count.ToString()),
                0f, 0f, maxWidth * 0.25f, 9f, Fonts.RobotoFontFamily, 7f, false));

            if (int.TryParse(Math.Round(meiBenchmark.SubIndustryPerformanceRisk.Percentile * 100, 0, MidpointRounding.AwayFromZero).ToString(), out percentile))
                row.Cells.Add(ReportHelper.AddOrdinal(percentile), Fonts.RobotoBold, 7f);
            else
                row.Cells.Add("N/A", Fonts.RobotoBold, 7f);

            page.Elements.Add(benchmarkTable);

        }




        private void AddMaterialIssues_SecondPage(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth, int PageNo)
        {
             AddIndicatorTable(issue, page, x + XRightColumn, y, ColumnWidth, _report.PageMaxHeight, PageNo);
          
        }

        //private void AddMaterialIssues_FourthPage(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        //{
        //    float currentYOffset = y + (float)VerticalSpacing.Small;

        //    currentYOffset = AddRatingDetails(issue, page, x, currentYOffset, ColumnWidth);
        //    currentYOffset = AddIssueRiskExposure(issue, page, x, currentYOffset, ColumnWidth);
        //    currentYOffset = AddManagement(issue, page, x, currentYOffset, ColumnWidth - 10);
        //    var maxHeight = currentYOffset;

        //    currentYOffset += 20;
        //    page.Elements.Add(new Line(x, currentYOffset, x + maxWidth, currentYOffset, 1, Colors.LineColor));

        //    currentYOffset = y;
        //    AddIndicatorTable(issue, page, x + XRightColumn, currentYOffset, ColumnWidth, maxHeight);

        //    AddIndicators(issue, page, x, maxHeight + 30f);
        //}


        private float AddIndicatorTable(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth, float maxHeight, int PageNo)
        {

            float currentYOffset = y+40f;
            x =10f;
      
            maxWidth = maxWidth + 250f;

            var management_details_image = ReportHelper.GetFile("icon-management.png");
            page.Elements.Add(new Image(ImageData.GetImage(management_details_image), 0, y, 0.3f));
            page.Elements.Add(new Label("Management Overview", 35f, y + 10f, 150f, 12f, Fonts.MontserratBold, 10f, TextAlign.Left, RgbColor.Black));
            page.Elements.Add(new Line(160, y+15f, _report.PageMaxWidth, y+15f, 1, RgbColor.Black));

            Table indicatorsTable = PdfReportSectionGenerator.GetDefaultTable(x, currentYOffset, maxWidth, maxHeight);

            indicatorsTable.CellDefault.VAlign = VAlign.Center;
          
            indicatorsTable.Columns.Add(maxWidth * 0.05f);
            indicatorsTable.Columns.Add(maxWidth * 0.50f);
            indicatorsTable.Columns.Add(maxWidth * 0.15f);
            indicatorsTable.Columns.Add(maxWidth * 0.15f);
            indicatorsTable.Columns.Add(maxWidth * 0.15f);

            var row = indicatorsTable.Rows.Add(20);
            row.Cells.Add(new Label(String.Empty, 0.0f, 0.0f, maxWidth * 0.50f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label("Indicators", 0.0f, 0.0f, maxWidth * 0.50f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label("Raw score", 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label("Weight", 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label("Weighted Score", 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Center, RgbColor.Black));
            row.CellDefault.Border.Bottom.LineStyle = LineStyle.Solid;
            row.CellDefault.Border.Bottom.Width = 1f;
            row.CellDefault.Border.Color = RgbColor.Black;


            currentYOffset += row.ActualRowHeight;

            var indicators = issue.Indicators
                .Where(i => i.IndicatorType == IndicatorType.StandardIndicator)
                .OrderByDescending(i => i.RawScore.Value)
                .ThenBy(i=> i.Name)
                .ToList();

            double totalWeightedScore = 0;

            foreach (var indicator in indicators)
            {
                row = indicatorsTable.Rows.Add(15);
                row.Cells.Add(new Label(String.Empty, 0.0f, 0.0f, maxWidth * 0.50f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
                row.Cells.Add(new Label(indicator.Name, 0.0f, 0.0f, maxWidth * 0.50f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
                row.Cells.Add(new Label(indicator.RawScore.Value.ToString("0"), 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
                row.Cells.Add(new Label(indicator.WeightInMei.Value.ToString("0.0%"), 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
                row.Cells.Add(new Label(indicator.WeightedScoreInMei.Value.ToString("0.0"), 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Center, RgbColor.Black));
                row.CellDefault.Border.Bottom.LineStyle = LineStyle.Solid;
                row.CellDefault.Border.Bottom.Width = 0.25f;
                row.CellDefault.Border.Color = new RgbColor(112, 112, 112);

                PageElementPositions.Add(new PageElementPosition
                {
                    Name = issue.Name + "_" + indicator.Name,
                    PageNumber = PageNo-1,
                    HorizontalPosition = x,
                    VerticalPosition = currentYOffset,
                    Width = maxWidth * 0.33f,
                    Height = row.ActualRowHeight,
                });

                currentYOffset += row.ActualRowHeight;
                totalWeightedScore += indicator.WeightedScoreInMei.Value;
            }
            var eventsSortedList = issue.Indicators.Where(a => a.IndicatorType == IndicatorType.EventIndicator).OrderByDescending(a => a.AnswerCategory.Value).ThenBy(a => a.Name);
            foreach (var indicator in eventsSortedList)
            {
                row = indicatorsTable.Rows.Add(15);
                row.Cells.Add(new Image(ImageData.GetImage(ReportHelper.GetEventImage(indicator.AnswerCategory.Value)), 0, 0, 0.1f));
                row.Cells.Add(indicator.Name, Fonts.RobotoRegular, 7);
                var category = indicator.AnswerCategoryText;
                if (indicator.AnswerCategoryText == "No evidence of relevant controversies") {
                    category = "Category 0";
                }
                row.Cells.Add(category, Fonts.RobotoRegular, 7);
                row.Cells.Add(indicator.WeightInMei.Value.ToString("0.0%"), Fonts.RobotoRegular, 7);
                row.Cells.Add(new Label(indicator.WeightedScoreInMei.Value.ToString("0.0"), 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoBold, 7f, TextAlign.Center, RgbColor.Black));
                row.CellDefault.Border.Bottom.LineStyle = LineStyle.Solid;
                row.CellDefault.Border.Bottom.Width = 0.25f;
                row.CellDefault.Border.Color = new RgbColor(112, 112, 112);
                currentYOffset += row.ActualRowHeight;
            }

            page.Elements.Add(indicatorsTable);

           
            row = indicatorsTable.Rows.Add(20);
            row.Cells.Add(new Label(String.Empty, 0.0f, 0.0f, maxWidth * 0.50f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label("Total", 0.0f, 0.0f, maxWidth * 0.50f, 7f, Fonts.RobotoBold, 7f, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label(String.Empty, 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label("100.0%", 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoBold, 7f, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label(totalWeightedScore.ToString("0.0"), 0.0f, 0.0f, maxWidth * 0.15f, 7f, Fonts.RobotoBold, 7f, TextAlign.Center, RgbColor.Black));
          
            currentYOffset += 30;

            var startingPos = 17f;
        
            page.Elements.Add(new Line(startingPos, currentYOffset - 2f, startingPos - 4f, currentYOffset - 8f, 0.5f, RgbColor.Black));
            page.Elements.Add(new Line(startingPos - 4f, currentYOffset - 8f, startingPos - 8f, currentYOffset - 2f, 0.5f, RgbColor.Black));
            page.Elements.Add(new Line(startingPos - 8f, currentYOffset - 2f, startingPos, currentYOffset - 2f, 0.5f, RgbColor.Black));
            page.Elements.Add(new Label("  =Event indicator", startingPos, currentYOffset-9f, 150f, 9f, Fonts.RobotoRegular, 6f, TextAlign.Left, RgbColor.Black));

            return currentYOffset;
        }

        private float AddManagement(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            float currentYOffset = y;

            page.Elements.Add(new Label("Management".ToUpper(), x, currentYOffset, maxWidth, (float)TextSizes.SubSectionTitle, Fonts.MontserratRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.LightGrey));
            currentYOffset += 20;

            RiskRating_RangeBarChart chartObj = new RiskRating_RangeBarChart();
            chartObj.Left = x;
            chartObj.Top = currentYOffset;
            chartObj.Width = maxWidth;
            chartObj.Value1 = (float)issue.ManagementRisk.Exposure.Value;
            chartObj.Value2 = (float)issue.ManagementRisk.ManageableRisk.Value;
            chartObj.Value3 = (float)issue.ManagementRisk.ManagedRisk.Value;
            chartObj.Value4 = (float)issue.ManagementRisk.Management.Value;
            chartObj.BarHeight = 10f;
            chartObj.ChartType = RangeChartType.MEI_Management;
            chartObj.CompanyName = _dataSource.CompanyProfile.CompanyName;
            page.Elements.Add(chartObj);
            currentYOffset += 50;

            double percent = Math.Round((chartObj.Value2 / chartObj.Value1) * 100,0,MidpointRounding.AwayFromZero);
            var chartText = string.Format("{0}% of the total issue risk exposure is manageable. As such, the management score is applied to this {0}% of the issue risk exposure.", percent);

            page.Elements.Add(new Line(x, currentYOffset, x + maxWidth, currentYOffset, 0.5f, Colors.LineColor));
            currentYOffset += 10;

            page.Elements.Add(new Label(chartText,
                                x,
                                currentYOffset,
                                maxWidth,
                                50,
                                Fonts.RobotoRegular, 6, TextAlign.Left, RgbColor.Black));
            currentYOffset += 20;

            return currentYOffset;
        }

        private float AddIssueRiskExposure(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            float currentYOffset = y;

            page.Elements.Add(new Label("Issue Risk Exposure".ToUpper(), x, currentYOffset, maxWidth, (float)TextSizes.SubSectionTitle, Fonts.MontserratRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));
            currentYOffset += 20;
            var industryValue = (float)issue.SubIndustryExposureScore.Value;
            var companyValue = (float)issue.ManagementRisk.Exposure.Value;
            var finalBetaFactor = (float)issue.FinalBetaFactor.Value;

            RiskRating_RangeBarChart chartObj = new RiskRating_RangeBarChart();
            chartObj.Left = x;
            chartObj.Top = currentYOffset;
            chartObj.Width = maxWidth;
            chartObj.Value1 = industryValue;
            chartObj.Value2 = companyValue;
            chartObj.BarHeight = 10f;
            chartObj.ChartType = RangeChartType.MEI_IssueRiskExposure;
            chartObj.CompanyName = _dataSource.CompanyProfile.CompanyName;
            chartObj.SubIndustryName = _dataSource.CompanyProfile.SubPeerGroup;
            chartObj.Render();
            page.Elements.Add(chartObj);

            //add legend
            var labelWidth = 100f;
            var left = chartObj.LeftBar - labelWidth - 20f - 14f;
            var top = chartObj.TopBar - 6f;

            var displayValue = companyValue - industryValue;
            
            page.Elements.Add(new Label("Relative Exposure - Subindustry",
                                left,
                                top,
                                labelWidth,
                                9,
                                Fonts.RobotoRegular, 7, TextAlign.Right, RgbColor.Black));
            page.Elements.Add(new Label((displayValue > 0 ? "+" : "") + displayValue.ToString("0.0"),
                                left + labelWidth + 4f,
                                top,
                                20f,
                                9,
                                Fonts.RobotoBold, 7, TextAlign.Right, RgbColor.Black));
            top += 15;


            displayValue = (finalBetaFactor - 1) * 100;

            page.Elements.Add(new Label("Excess Exposure - Subindustry",
                                left,
                                top,
                                labelWidth,
                                9,
                                Fonts.RobotoRegular, 7, TextAlign.Right, RgbColor.Black));
            page.Elements.Add(new Label((displayValue>0?"+":"") + displayValue.ToString("0")+"%",
                                left + labelWidth + 4f,
                                top,
                                20f,
                                9,
                                Fonts.RobotoBold, 7, TextAlign.Right, RgbColor.Black));
            top += 15;


            page.Elements.Add(new Label("Beta",
                                left,
                                top,
                                labelWidth,
                                9,
                                Fonts.RobotoRegular, 7, TextAlign.Right, RgbColor.Black));
            page.Elements.Add(new Label(finalBetaFactor.ToString("0.00"),
                                left + labelWidth + 4f,
                                top,
                                20f,
                                9,
                                Fonts.RobotoBold, 7, TextAlign.Right, RgbColor.Black));

            currentYOffset += 100f;

            return currentYOffset;
        }

        private float AddRatingDetails(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float y, float maxWidth)
        {
            float currentYOffset = y;
            page.Elements.Add(new Line(0, currentYOffset-5f, _report.PageMaxWidth, currentYOffset-5f ,1, Colors.LineColor));
            page.Elements.Add(new Label("Rating Overview", x, currentYOffset, maxWidth, (float)TextSizes.SubSectionTitle, Fonts.RobotoBold, (float)TextSizes.SubSectionTitle+2f, TextAlign.Left, RgbColor.Black));
            currentYOffset += 20;
            page.Elements.Add(new RiskRating_CustomBulletChart
            {
                Top = currentYOffset,
                Left = x,
                Width = maxWidth,
                Value = issue.ManagementRisk.UnmanagedRisk,
                Assessment = issue.Cluster.Assessment.ToString(),
                RiskRatingClusterList = _dataSource.MaterialIssuesClusters,
                BarHeight = 15
            });

            var exposureScore = issue.ManagementRisk.Exposure.Value.ToString("#0.0");
            var assesmentExposure = issue.ExposureCluster.ToString();
            var left = x + maxWidth;
            page.Elements.Add(new Label("Risk Analysis", left, currentYOffset-20f, maxWidth, (float)TextSizes.SubSectionTitle, Fonts.RobotoBold, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));
            page.Elements.Add(new Label("Exposure", left + 3f, currentYOffset, maxWidth, 10, Fonts.RobotoBold, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));
            currentYOffset += 10;
            page.Elements.Add(new Label(exposureScore, left + 3f, currentYOffset+5, maxWidth, 10, Fonts.RobotoRegular, 7, TextAlign.Left, RgbColor.Black));
            page.Elements.Add(new Label(assesmentExposure, left + 25f, currentYOffset + 5f, maxWidth, 10, Fonts.RobotoRegular, 7, TextAlign.Left, RgbColor.Black));

            RiskRating_RiskAnalysisRangeChart chartObjExposure = new RiskRating_RiskAnalysisRangeChart();
            chartObjExposure.Top = currentYOffset+5f;
            chartObjExposure.Left = left + maxWidth/3;
            chartObjExposure.Width = 20f;
            chartObjExposure.ChartType = RiskChartType.MEI;
            chartObjExposure.Type = "Exposure";
            chartObjExposure.Value = (float)issue.ManagementRisk.Exposure.Value;
            chartObjExposure.Assessment = issue.ExposureCluster.ToString();
            chartObjExposure.ExposureClusterList = _dataSource.ExposureClusters.Where(s => s.Type == RiskRatingClusterType.MEI).ToList();
            page.Elements.Add(chartObjExposure);

            currentYOffset += 40;

            page.Elements.Add(new Label("Management", left + 3f, currentYOffset, maxWidth, 10, Fonts.RobotoBold, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));

            currentYOffset += 10;

            var managementScore = issue.ManagementRisk.Management.Value.ToString("#0.0");
            var assesmentManagement = issue.ManagementCluster.ToString();
            page.Elements.Add(new Label(managementScore, left + 3f, currentYOffset + 5f, maxWidth, 10, Fonts.RobotoRegular, 7, TextAlign.Left, RgbColor.Black));
            page.Elements.Add(new Label(assesmentManagement, left + 25f, currentYOffset + 5f, maxWidth, 10, Fonts.RobotoRegular, 7, TextAlign.Left, RgbColor.Black));
            if (issue.ManagementRisk.Management.Value != 0)
            {
                RiskRating_RiskAnalysisRangeChart chartObjManagement= new RiskRating_RiskAnalysisRangeChart();
                chartObjManagement.Top = currentYOffset + 5f;
                chartObjManagement.Left = left + maxWidth / 3;
                chartObjManagement.Width = 20f;
                chartObjManagement.Type = "Management";
                chartObjManagement.Value = (float)issue.ManagementRisk.Exposure.Value;
                chartObjManagement.Assessment = issue.ExposureCluster.ToString();
                chartObjManagement.ManagementClusterList = _dataSource.ManagementClusters.Where(s => s.Type == RiskRatingClusterType.MEI).ToList();
                page.Elements.Add(chartObjManagement);
            }
            else
            {
                page.Elements.Add(new Label("Idiosyncratic issues are represented only by the event indicator for the issue. The management score for idiosyncratic issues is always 0.", left + maxWidth / 3, currentYOffset-10f, 175f, 70f, Fonts.RobotoRegular, 7f, TextAlign.Left, RgbColor.Black));
            }

             currentYOffset += 10;
            
            if (issue.AnalystViewComment != null && !string.IsNullOrWhiteSpace(issue.AnalystViewComment.Value))
            {
                var style = new FormattedTextAreaStyle(Fonts.RobotoFontFamily, 7f, false)
                {
                    Paragraph = { Align = TextAlign.Left, Indent = 0, SpacingAfter = 0, AllowOrphanLines = false }
                };
                var analystCommentTextArea = new FormattedTextArea(issue.AnalystViewComment.Value, x + 10f, currentYOffset + 20, x + maxWidth - 20f, 45f, style);
                page.Elements.Add(new Line(x, currentYOffset + 35f, x + maxWidth, currentYOffset + 35f, analystCommentTextArea.GetRequiredHeight() + 15f, new RgbColor(236, 241, 246)));
                page.Elements.Add(analystCommentTextArea);

            }

            currentYOffset += 60;
            //add risk details
            var columnWidth = (maxWidth - (float)HorisontalSpacing.Large) / 3;
            RiskRating_RiskRangeBarChart chartObj = new RiskRating_RiskRangeBarChart();
            chartObj.Left = x;
            chartObj.Top = currentYOffset+30f;
            chartObj.Width = columnWidth+100f;
            chartObj.Value1 = issue.ManagementRisk.Exposure.Value;
            chartObj.Value2 = issue.ManagementRisk.ManageableRisk.Value;
            chartObj.Value3 = issue.ManagementRisk.ManagedRisk.Value;
            chartObj.Value4 = issue.ManagementRisk.ManagementGap.Value;
            chartObj.Value5 = issue.ManagementRisk.UnmanageableRisk.Value;
            chartObj.Value6 = issue.ManagementRisk.UnmanagedRisk.Value;
            chartObj.BarHeight = 10f;
            chartObj.ChartType = RiskRangeChartType.IssueRiskDetails;
            page.Elements.Add(chartObj);
            currentYOffset += currentYOffset;

            return currentYOffset;
        }

        #endregion

        #region Indicator section

        private void AddIndicators(RiskRatingMaterialEsgIssueBase issue, PdfReportPage page, float x, float top)
        {
            var maxWidth = 255f;

            page.Elements.Add(new Label("Indicators Details".ToUpper(), x, top, maxWidth, (float)TextSizes.SubSectionTitle, 
                Fonts.MontserratRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));
            top += 20;

            var standardIndicators = issue.Indicators
                .Where(i => i.IndicatorType == IndicatorType.StandardIndicator)
                .OrderBy(i => i.SortKey.Value)
                .ToList();

            if (!standardIndicators.Any()) return;

            var maxHeight = _report.PageMaxHeight - top;

            PdfReportPage nextPage = null;
            Table firstTable = null;
            Table secondTable = null;
            bool isNewPage = false;

            for (var skip = 1; skip <= standardIndicators.Count; skip += 2)
            {
                if (nextPage == null && skip > 2 && top > 600f)
                {
                    page = new PdfReportPage_MaterialIssues(_report, _dataSource, issue, ReportHelper.GetMeiImage(issue.ExternalId.ToString(), MeiImageColor.Colored, MeiImageSize.Large, issue.Type == MaterialIssueType.IdiosyncraticIssue));
                    _report.Pages.Add(page);
                    OutlinePageCount++;

                    top = page.Top + 20f; 
                }

                maxHeight = _report.PageMaxHeight - top;

                float firstRequiredHeight = 0.0f;
                float secondRequiredHeight = 0.0f;

                var firstIndicator = standardIndicators.Skip(skip - 1).Take(1).SingleOrDefault();

                if (firstIndicator != null)
                {
                    firstTable = GetIndicatorTable(firstIndicator, x, top, maxWidth, maxHeight);
                    page.Elements.Add(firstTable);
                    firstRequiredHeight = firstTable.GetRequiredHeight();
                }

                var secondIndicator = standardIndicators.Skip(skip).Take(1).SingleOrDefault();

                if (secondIndicator != null)
                {
                    secondTable = GetIndicatorTable(secondIndicator, x + maxWidth + 30f, top, maxWidth, maxHeight);
                    page.Elements.Add(secondTable);
                    secondRequiredHeight = secondTable.GetRequiredHeight();
                }

                top += firstRequiredHeight > secondRequiredHeight ? firstRequiredHeight : secondRequiredHeight;

                firstRequiredHeight = 0;
                secondRequiredHeight = 0;

                if (firstIndicator != null && firstTable != null)
                {
                    var overflowTable = firstTable.GetOverflowRows();

                    if (overflowTable != null)
                    {
                        isNewPage = true;

                        page = new PdfReportPage_MaterialIssues(_report, _dataSource, issue, ReportHelper.GetMeiImage(issue.ExternalId.ToString(), MeiImageColor.Colored, MeiImageSize.Large, issue.Type == MaterialIssueType.IdiosyncraticIssue));
                        _report.Pages.Add(page);
                        OutlinePageCount++;

                        top = page.Top + 20f;

                        maxHeight = _report.PageMaxHeight - top;

                        firstRequiredHeight = overflowTable.GetRequiredHeight();

                        overflowTable.Y = top;
                        overflowTable.Height = firstRequiredHeight;

                        page.Elements.Add(overflowTable);
                    }
                }

                if (secondIndicator != null && secondTable != null)
                {
                    var overflowTable = secondTable.GetOverflowRows();

                    if (overflowTable != null)
                    {
                        if (!isNewPage)
                        {
                            page = new PdfReportPage_MaterialIssues(_report, _dataSource, issue, ReportHelper.GetMeiImage(issue.ExternalId.ToString(), MeiImageColor.Colored, MeiImageSize.Large, issue.Type == MaterialIssueType.IdiosyncraticIssue));
                            _report.Pages.Add(page);
                            OutlinePageCount++;

                            top = page.Top + 20f;

                            maxHeight = _report.PageMaxHeight - top;
                        }

                        secondRequiredHeight = overflowTable.GetRequiredHeight();

                        overflowTable.Y = top;
                        overflowTable.Height = secondRequiredHeight;

                        page.Elements.Add(overflowTable);
                    }
                }


                top += firstRequiredHeight > secondRequiredHeight ? firstRequiredHeight : secondRequiredHeight;

                top += 10f;

                page.Elements.Add(new Line(x, top, _report.PageMaxWidth, top, 1, Colors.LineColor, LineStyle.Dots));

                top += 20f;

                isNewPage = false;
            }

        }

        private Table GetIndicatorTable(ComprehensiveRiskRatingIndicator indicator, float x, float y, float maxWidth, float maxHeight)
        {
            // 1.  Indicator code and name

            var indicatorName = $"{indicator.Code} - {indicator.Name}";

            Table table = GetDefaultTable(x, y, maxWidth, maxHeight);

            table.CellDefault.Border.Bottom.LineStyle = LineStyle.None;
            table.CellDefault.Border.Bottom.Width = 0.5f;
            table.CellDefault.Border.Color = RgbColor.Black;
            table.CellDefault.VAlign = VAlign.Center;

            table.Columns.Add(maxWidth*0.33f);
            table.Columns.Add(maxWidth*0.33f);
            table.Columns.Add(maxWidth*0.34f);

            var row = table.Rows.Add(15);
            row.Cells.Add(new TextArea(indicatorName, 0.0f, 0.0f, maxWidth, 12*2.5f,
                Fonts.RobotoBold, 12, TextAlign.Left, RgbColor.Black), 3);

            row = table.Rows.Add(10);
            row.Cells.Add(new Line(0, 5f, maxWidth, 5f, 0.5f, RgbColor.Silver, LineStyle.Dots), 3);

            // 2. Raw Score, Weight, Weighted Score

            row = table.Rows.Add(15);
            row.Cells.Add(new Label(indicator.RawScore.Value.ToString(" #0              x"), 0.0f, 0.0f, maxWidth, 11,
                Fonts.RobotoBold, 9, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label(indicator.WeightInMei.Value.ToString("#0.00%            ="), 0.0f, 0.0f, maxWidth, 11,
                Fonts.RobotoBold, 9, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label(indicator.WeightedScoreInMei.Value.ToString("#0.0"), 0.0f, 0.0f, maxWidth, 11,
                Fonts.RobotoBold, 9, TextAlign.Left, RgbColor.Black));

            row = table.Rows.Add(10);
            row.Cells.Add(new Label("Raw Scoreee", 0.0f, 0.0f, maxWidth, 9,
                Fonts.RobotoBold, 7, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label("Weight", 0.0f, 0.0f, maxWidth, 9,
                Fonts.RobotoBold, 7, TextAlign.Left, RgbColor.Black));
            row.Cells.Add(new Label("Weighted Score", 0.0f, 0.0f, maxWidth, 9,
                Fonts.RobotoBold, 7, TextAlign.Left, RgbColor.Black));

            // 3. Answer Category

            if (!string.IsNullOrEmpty(indicator.AnswerCategoryText))
            {
                row = table.Rows.Add(10f);
                row.Cells.Add(new Line(0, 5f, maxWidth, 5f, 0.5f, RgbColor.Silver, LineStyle.Dots), 3);

                var answerCategoryTextArea = new FormattedTextArea($"<b>{indicator.AnswerCategoryText}</b>", 0f, 0f, maxWidth, 100f, Fonts.RobotoFontFamily, 10f, false);
                var answerCategoryTextHeight = (int)answerCategoryTextArea.GetRequiredHeight() + 5f;

                row = table.Rows.Add(answerCategoryTextHeight);
                row.Cells.Add(new FormattedTextArea($"<b>{indicator.AnswerCategoryText}</b>", 0f, 0f, maxWidth, answerCategoryTextHeight, Fonts.RobotoFontFamily, 10f, false));
            }

            // 4. Analyst Commentary

            if (!string.IsNullOrEmpty(indicator.Comment.Value))
            {
                row = table.Rows.Add(10f);
                row.Cells.Add(new Line(0, 5f, maxWidth, 5f, 0.5f, RgbColor.Silver, LineStyle.Dots), 3);

                var commentTextArea = new FormattedTextArea($"<p>{indicator.Comment.Value}</p>", 0f, 0f, maxWidth, 100f, Fonts.RobotoFontFamily, 7f, false);
                var commentTextHeight = (int)commentTextArea.GetRequiredHeight() + 5f;

                row = table.Rows.Add(commentTextHeight);
                row.Cells.Add(new FormattedTextArea($"<p>{indicator.Comment.Value}</p>", 0f, 0f, maxWidth, commentTextHeight, Fonts.RobotoFontFamily, 7f, false));
            }

            // 5. Tick boxes

            var checkbox_on_image = ReportHelper.GetFile("indicator_checkbox_on.png");
            var checkbox_off_image = ReportHelper.GetFile("indicator_checkbox_off.png");

            if (indicator.CheckBoxes.Any())
            {
                row = table.Rows.Add(10f);
                row.Cells.Add(new Line(0, 5f, maxWidth, 5f, 0.5f, RgbColor.Silver, LineStyle.Dots), 3);

                row = table.Rows.Add(15);
                row.Cells.Add(new Label("Criteria", 0.0f, 0.0f, maxWidth, 9,
                    Fonts.RobotoBold, 7, TextAlign.Left, RgbColor.Black));

                foreach (var checkBox in indicator.CheckBoxes)
                {
                    
                    var checkBoxTextArea = new FormattedTextArea($"<p>{checkBox.Text}</p>", 15f, 0f, maxWidth - 15f, 100f, Fonts.RobotoFontFamily, 7f, false);
                        var checkBoxTextHeight = (int)checkBoxTextArea.GetRequiredHeight() + 5f;

                    var group = new Group();

                    group.Add(checkBox.IsChecked.Value 
                        ? new Image(ImageData.GetImage(checkbox_on_image), 0.0f, 0.0f, 0.11f) { Align = Align.Left, VAlign = VAlign.Top } 
                        : new Image(ImageData.GetImage(checkbox_off_image), 0.0f, 0.0f, 0.11f) { Align = Align.Left, VAlign = VAlign.Top });

                    group.Add(new FormattedTextArea($"<p>{checkBox.Text}</p>", 15f, 0f, maxWidth - 15f, checkBoxTextHeight, Fonts.RobotoFontFamily, 7f, false));


                    row = table.Rows.Add(checkBoxTextHeight);
                    row.Cells.Add(group);
                }
            }

            // 6. Sources

            if (indicator.Sources.Any())
            {
                row = table.Rows.Add(10f);
                row.Cells.Add(new Line(0, 5f, maxWidth, 5f, 0.5f, RgbColor.Silver, LineStyle.Dots), 3);

                row = table.Rows.Add(15);
                row.Cells.Add(new Label("Sources", 0.0f, 0.0f, maxWidth, 9,
                    Fonts.RobotoBold, 7, TextAlign.Left, RgbColor.Black));

                foreach (var source in indicator.Sources.OrderBy(s => s))
                {
                    var sourceTextArea = new FormattedTextArea($"<p>{source}</p>", 0f, 0f, maxWidth, 100f, Fonts.RobotoFontFamily, 7f, false);
                    var sourceTextHeight = (int)sourceTextArea.GetRequiredHeight() + 5f;

                    row = table.Rows.Add(sourceTextHeight);
                    row.Cells.Add(new FormattedTextArea($"<p>{source}</p>", 0f, 0f, maxWidth, sourceTextHeight, Fonts.RobotoFontFamily, 7f, false));
                }
            }

            return table;
        }

        #endregion

        #region Events Section
        private void AddMaterialIssues_EventsPage(RiskRatingMaterialEsgIssueBase issue, float x, float y, float maxWidth, PdfReportPage page)
        {
            CurrentIssue = issue;
            CurrentPage = page;
            Event_LeftYOffset = Event_CurrentYOffset = y + (float)VerticalSpacing.Small;

            var indicatorsCode = issue.Indicators.Where(i => i.IndicatorType == IndicatorType.EventIndicator).Select(i => new { i.Code, i.SortKey, i.AnswerCategory });

            var joinResult = _dataSource.Events.Join(indicatorsCode, i => i.CanvasCode, mei => mei.Code, (i, mei) =>
            {
                i.EventCategory = mei.AnswerCategory.Value;
                return new { Indicator = i, MEI = mei };
            });


            if (joinResult == null || !joinResult.Any())
            {
                return;
            }

            var eventIndicators = joinResult.OrderByDescending(i => i.Indicator.EventCategory)
                                    //.ThenBy(i=>i.MEI.SortKey.Value)
                                    .ThenBy(i => i.Indicator.Name)
                                    .Select(i => i.Indicator)
                                    .Where(i => i.EventCategory > 0)
                                    .ToList();

            if (page != null && issue.Type == MaterialIssueType.IdiosyncraticIssue && eventIndicators.Any())
            {
                CurrentPage = page;
                Event_CurrentYOffset = y + (float)VerticalSpacing.Small;
                Event_CurrentXOffset = 0;
                var eventIndicator = eventIndicators.First();
                var associatedIncidents = _dataSource.Incident.Where(i => i.EventIndicatorId == eventIndicator.Id).OrderByDescending(i => i.IncidentDate);
                    Event_LeftYOffset = AddEventsFirstPage(eventIndicator, associatedIncidents, Event_CurrentXOffset, Event_CurrentYOffset);
                Event_CurrentXOffset = XRightColumn;
                //foreach (var incidentGroup in associatedIncidents.GroupBy(i => i.IncidentId))
                //{
                //    AddIncindetGroup(incidentGroup, Event_CurrentXOffset, Event_CurrentYOffset);
                //}
                Event_CurrentYOffset = Math.Max(Event_LeftYOffset, Event_CurrentYOffset);
            }
            else
            {
                foreach (var eventIndicator in eventIndicators)
                {
                    var associatedIncidents = _dataSource.Incident.Where(i => i.EventIndicatorId == eventIndicator.Id).OrderByDescending(i => i.IncidentDate);

                    if (eventIndicator.EventCategory >= 3 || CheckNewPageOrNewSection(Event_CurrentYOffset) || associatedIncidents.Any())
                    { AddNewPage(); }
                    else
                    { AddNewEventSection(); }

                    Event_LeftYOffset = AddEventsFirstPage(eventIndicator, associatedIncidents, Event_CurrentXOffset, Event_CurrentYOffset);

                    Event_CurrentXOffset = XRightColumn;
                    foreach (var incidentGroup in associatedIncidents.GroupBy(i => i.IncidentId))
                    {
                        AddIncindetGroup(incidentGroup, Event_CurrentXOffset, Event_CurrentYOffset);
                    }
                    Event_CurrentYOffset = Math.Max(Event_LeftYOffset, Event_CurrentYOffset);
                }
            }
        }

        private float AddEventsFirstPage(EventIndicator eventIndicator, IEnumerable<Incident> incidents, float x, float y)
        {
            var eventSectionHeader = AddEventHeader(eventIndicator, x, y);
            var currentXOffset = x;
            var currentYOffset = eventSectionHeader.Item1;
            if (CheckNewPageOrNewSection(eventSectionHeader.Item1))
            {
                AddNewPage();
                currentXOffset = Event_CurrentXOffset;
                currentYOffset = Event_CurrentYOffset;
                eventSectionHeader = AddEventHeader(eventIndicator, currentXOffset, currentYOffset);
                currentYOffset = eventSectionHeader.Item1;
            }
            CurrentPage.Elements.Add(eventSectionHeader.Item2);

            currentYOffset += (float)VerticalSpacing.Small;

            return currentYOffset;

        }

        private Tuple<float,Group> AddEventHeader(EventIndicator issue, float x, float currentYOffset)
        {

            var group = new Group();
            currentYOffset += 20;
            var image = new Image(ImageData.GetImage(ReportHelper.GetEventImage(issue.EventCategory)), x, currentYOffset-10f, 0.33f);
            group.Add(image);
            //x = x + 30f;
            //outlook image
            //var outlookImage = new Image(ImageData.GetImage(ReportHelper.GetEventImage(issue.EventCategory)), x, currentYOffset, 0.33f);
            //group.Add(outlookImage);
            group.Add(new Label("Category "+ issue.EventCategory + " Event - " + issue.EventCategoryText, x + 50f, currentYOffset, ColumnWidth, (float)TextSizes.RegularTextSubtitle, Fonts.RobotoBold, (float)TextSizes.SectionTitle, TextAlign.Left, RgbColor.Black));
           
            //group.Add(new Label(issue.ControversySummary, x + 50f, currentYOffset,ColumnWidth*2, 500f, Fonts.RobotoBold, (float)TextSizes.SectionTitle, TextAlign.Left, RgbColor.Black));
            //currentYOffset += (float)TextSizes.SectionTitle + (float)VerticalSpacing.Small;

            if (issue.EventCategory >= 3)
            {
                var outlookLabelImageWidth = 18f;
                if (issue.OutlookLabel != null)
                {                    
                    var arroImage = new Image(ImageData.GetImage(ReportHelper.GetOutlookImage($"icon_outlook_{issue.OutlookLabel.ToLower() ?? string.Empty}_large")), x + 200f, currentYOffset - 7f, 0.3f);
                    //var arroImage = new Image(ImageData.GetImage("icon-cat1.svg"), x + 200f, currentYOffset - 7f, 0.3f);
                    outlookLabelImageWidth = arroImage.Width;
                    group.Add(arroImage);
                    group.Add(new Label("Outlook - " + issue.OutlookLabel, x + 205f + arroImage.Width, currentYOffset, ColumnWidth, (float)TextSizes.RegularTextSubtitle, Fonts.RobotoBold, (float)TextSizes.SectionTitle, TextAlign.Left, RgbColor.Black));
                }

                currentYOffset += image.Height;
                //currentYOffset += 20;
                //elements.Add(new Label("Outlook", currentX, currentYOffset, ColumnWidth, (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));

                //currentX += outlookLabelImageWidth;

                //elements.Add(new Label(issue.OutlookLabel ?? string.Empty, currentX, currentY, ColumnWidth / 2, (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));
            }

            //var outlookItems = AddOutlook(issue, x, currentYOffset);

            //group.Add(outlookItems.Item2);

            var analystItems = AddEventsAnalystCommentary(issue, XRightColumn, currentYOffset);

            group.Add(analystItems.Item2);

            //currentYOffset = Math.Max(outlookItems.Item1, analystItems.Item1) + (float)VerticalSpacing.Large;

            return new Tuple<float,Group> (currentYOffset,group);
        }

        private Tuple<float,Group> AddOutlook(EventIndicator issue, float x, float currentYOffset)
        {
            var elements = new Group();

            var image = new Image(ImageData.GetImage(ReportHelper.GetEventImage(issue.EventCategory)), x, currentYOffset, 0.33f);
            elements.Add(image);
            var currentX = x + image.Width;
            var currentY = currentYOffset + (image.Height - (float)TextSizes.SubSectionTitle) / 2;

            elements.Add(new Label(issue.EventCategoryText, currentX, currentY, ColumnWidth / 2, (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));

            currentX = ColumnWidth / 2;

            if (issue.EventCategory >= 3)
            {
                var outlookLabelImageWidth = 18f;
                if (issue.OutlookLabel != null)
                {
                    var arroImage = new Image(ImageData.GetImage(ReportHelper.GetOutlookImage(issue.OutlookLabel ?? string.Empty)), currentX, currentYOffset + 7, 0.75f);
                    outlookLabelImageWidth = arroImage.Width;
                    elements.Add(arroImage);
                }

                currentYOffset += image.Height;
                elements.Add(new Label("Outlook", currentX, currentYOffset, ColumnWidth, (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));

                currentX += outlookLabelImageWidth;

                elements.Add(new Label(issue.OutlookLabel ?? string.Empty, currentX, currentY, ColumnWidth / 2, (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));
            }
            else
            {
                currentYOffset = currentY = currentYOffset + image.Height;
            }

            elements.Add(new Label("Event Category", x, currentYOffset, ColumnWidth, (float)TextSizes.SubSectionTitle, Fonts.RobotoRegular, (float)TextSizes.SubSectionTitle, TextAlign.Left, RgbColor.Black));

            currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;

            if (!string.IsNullOrEmpty(issue.OutlookText))
            {
                elements.Add(SectionTile("Outlook", x, currentYOffset));

                currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;

                FormattedTextArea textArea = new FormattedTextArea(issue.OutlookText, x, currentYOffset, ColumnWidth, 500, Fonts.RobotoFontFamily, (float)TextSizes.RegularTextSubtitle, false);
                elements.Add(textArea);

                currentYOffset += textArea.GetRequiredHeight() + (float)VerticalSpacing.Small;

                issue.OutlookComments?.ForEach(comment =>
                {
                    textArea = new FormattedTextArea(comment, x, currentYOffset, ColumnWidth, 500, Fonts.RobotoFontFamily, (float)TextSizes.RegularText, false);
                    elements.Add(textArea);
                    currentYOffset += textArea.GetRequiredHeight() + (float)VerticalSpacing.Small;
                });
            }

            return new Tuple<float,Group> (currentYOffset,elements);
        }

        private Label SectionTile(string title, float x, float y) => new Label(
                    title,
            x,
            y,
            _report.PageMaxWidth,
            (float)TextSizes.SubSectionTitle,
            Fonts.RobotoBold,
            (float)TextSizes.SubSectionTitle,
            TextAlign.Left,
            RgbColor.Black);

        private Tuple<float,Group> AddEventsAnalystCommentary(EventIndicator issue, float x, float y)
        {
            var elements = new Group();
            float currentYOffset = y;
            if (issue == null || string.IsNullOrEmpty(issue.ControversySummary))
                return new Tuple<float,Group>(currentYOffset,elements);

            //elements.Add(SectionTile("Assessment", x, currentYOffset));

            //currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;
            FormattedTextArea textAreaSummary = new FormattedTextArea("<b>Summary</b>", 0, currentYOffset, ColumnWidth, 500, Fonts.RobotoFontFamily, 9, false);
            currentYOffset += textAreaSummary.GetRequiredHeight()+5f;
            elements.Add(textAreaSummary);
            FormattedTextArea textArea = new FormattedTextArea(issue.ControversySummary, 0, currentYOffset, ColumnWidth, 500, Fonts.RobotoFontFamily, 7, false);
            elements.Add(textArea);

            //currentYOffset += textArea.GetRequiredHeight() + (float)VerticalSpacing.Small;

            //textArea = new FormattedTextArea(issue.EventJustification ?? string.Empty, x, currentYOffset, ColumnWidth, 500, Fonts.RobotoFontFamily, 7, false);
            //elements.Add(textArea);

            currentYOffset += textArea.GetRequiredHeight();

            return new Tuple<float, Group>(currentYOffset, elements);
        }
        private void AddNewEventSection()
        {
            Event_CurrentYOffset += (float)VerticalSpacing.Small;
            Event_CurrentXOffset = 0;

        }

        private float AddIncidentsMap(List<Incident> incidents, float x, float currentYOffset)
        {
            if (!incidents.Any())
            {
                Event_CurrentYOffset = currentYOffset;
                return currentYOffset;
            }
            CurrentPage.Elements.Add(SectionTile("Incident History", x, currentYOffset));

            currentYOffset += (float)TextSizes.SubSectionTitle + (float)VerticalSpacing.Small;

            Event_CurrentYOffset = currentYOffset;

            var map = new Image(ImageData.GetImage(IncidentsMap.GetMapImageOptimized(incidents.Select(l => l.Location).ToList(), (int)ColumnWidth, (int)ColumnWidth, MapSize.Big)), x, currentYOffset - ColumnWidth / 5, 0.98f);
            CurrentPage.AddElement(map);

            currentYOffset += ColumnWidth / 2 + (float)VerticalSpacing.Small;

            HashSet<string> addresses = new HashSet<string>();
            HashSet<string> tags = new HashSet<string>();
            incidents.ForEach(i =>
            {
                if (!addresses.Contains(i.Location.Address)) { addresses.Add(i.Location.Address); }
                if (!tags.Contains(i.MainTag)) { tags.Add(i.MainTag); }
            });

            if (addresses.Any())
            {
                var textArea = new FormattedTextArea("<b>Locations:</b> " + addresses.Aggregate((a, b) => a + ", " + b), x, currentYOffset, ColumnWidth, 500, Fonts.RobotoFontFamily, (float)TextSizes.RegularText, false);
                CurrentPage.Elements.Add(textArea);
                currentYOffset += textArea.GetRequiredHeight() + (float)VerticalSpacing.Small;
            }

            if (tags.Any())
            {
                var textArea = new FormattedTextArea("<b>Tags:</b> " + tags.Aggregate((a, b) => a + ", " + b), x, currentYOffset, ColumnWidth, 500, Fonts.RobotoFontFamily, (float)TextSizes.RegularText, false);
                CurrentPage.Elements.Add(textArea);
                currentYOffset += textArea.GetRequiredHeight() + (float)VerticalSpacing.Small;
            }
            return currentYOffset;
        }

        private void AddIncindetGroup(IGrouping<string, Incident> incidentGroup, float x, float y)
        {
            float currentYOffset = y;
            float currentXOffset = x;
            var incidents = incidentGroup.OrderByDescending(i => i.IncidentDate).ToArray();
            Tuple<float, Group> item;
            Incident mainIncident = incidents.FirstOrDefault(i => i.IsMain);

            if (mainIncident != null)
            {
                item = AddIncident(currentXOffset, currentYOffset, mainIncident);
                var incidentHeight = Math.Abs(currentYOffset - item.Item1);

                if (CheckNewPageOrNewSection(item.Item1 + incidentHeight))
                {
                    currentXOffset = Event_CurrentXOffset;
                    currentYOffset = Event_CurrentYOffset;
                    item = AddIncident(currentXOffset, currentYOffset, mainIncident);
                    currentYOffset = Event_CurrentYOffset = item.Item1;
                    CurrentPage.Elements.Add(item.Item2);
                }
                else
                {
                    currentYOffset = Event_CurrentYOffset = item.Item1;
                    currentXOffset = Event_CurrentXOffset;
                    CurrentPage.Elements.Add(item.Item2);
                }
            }

            foreach (var incident in incidents.Where(i => !i.IsMain))
            {
                if (incident != null)
                {
                    item = AddIncident(currentXOffset + 20, currentYOffset, incident, $"Update: {incident.Name}");

                    if (CheckNewPageOrNewSection(item.Item1))
                    {
                        currentXOffset = Event_CurrentXOffset;
                        currentYOffset = Event_CurrentYOffset;
                        item = AddIncident(currentXOffset, currentYOffset, mainIncident);
                        currentYOffset = item.Item1;
                        CurrentPage.Elements.Add(item.Item2);
                        item = AddIncident(currentXOffset + 20, currentYOffset, incident, $"Update: {incident.Name}");
                    }

                    currentYOffset = Event_CurrentYOffset = item.Item1;
                    currentXOffset = Event_CurrentXOffset;
                    CurrentPage.Elements.Add(item.Item2);
                }
            }

            Event_CurrentYOffset += (float)VerticalSpacing.Small;
        }

        private Tuple<float, Group> AddIncident(float x, float currentYOffset, Incident incident, string IncidentName = null)
        {
            var group = new Group();
            group.Add(new Label(
                IncidentName ?? incident.Name,
                x,
                currentYOffset,
                ColumnWidth,
                (float)TextSizes.RegularText,
                Fonts.RobotoBold,
                (float)TextSizes.RegularText,
                TextAlign.Left,
                RgbColor.Black));
            currentYOffset += (float)TextSizes.RegularText + 2;
            var labelText = $"{ incident.Source } - { incident.IncidentDate.ToString("dd MMMM yyyy") } ";
            var labelColor = RgbColor.Black;

            if (!string.IsNullOrWhiteSpace(incident.ExternalUrl))
            {
                labelColor = new RgbColor(255, 165, 0);
                var action = new UrlAction(incident.ExternalUrl);
                var incidentLink = new Link(x, currentYOffset, Fonts.RobotoBold.GetTextWidth(labelText, 7), (float)TextSizes.RegularText, action);
                group.Add(incidentLink);
            }

            var label = new Label(
                labelText,
                x,
                currentYOffset,
                ColumnWidth,
                (float)TextSizes.RegularText,
                Fonts.RobotoRegular,
                (float)TextSizes.RegularText,
                TextAlign.Left,
                labelColor);

            group.Add(label);

            currentYOffset += (float)TextSizes.RegularText + (float)VerticalSpacing.Small;
            return new Tuple<float, Group>(currentYOffset, group);
        }

        private bool CheckNewPageOrNewSection(float offset)
        {
            Event_CurrentYOffset = offset;
            if (CurrentPage == null)
            {

                return true;
            }
            if (offset >= CurrentPage.Dimensions.Height - CurrentPage.Top)
            {
                if (Event_CurrentXOffset >= XRightColumn)
                {
                    AddNewPage();
                    return true;
                }
                Event_CurrentXOffset = XRightColumn; Event_CurrentYOffset = CurrentPage.Top + (float)VerticalSpacing.Small;
                return true;
            }
            return false;
        }

        private void AddNewPage()
        {
            CurrentPage = new PdfReportPage_MaterialIssues(_report, _dataSource, CurrentIssue, ReportHelper.GetMeiImage(CurrentIssue.ExternalId.ToString(), MeiImageColor.Colored, MeiImageSize.Large, CurrentIssue.Type == MaterialIssueType.IdiosyncraticIssue));
            _report.Pages.Add(CurrentPage);
            OutlinePageCount++;
            Event_CurrentYOffset = Event_LeftYOffset =  CurrentPage.Top + (float)VerticalSpacing.Small;
            Event_CurrentXOffset = 0;
        }

        #endregion
    }
}
